home *** CD-ROM | disk | FTP | other *** search
- #ifdef COMMENT
-
- | testATP.c
- |
- | This program scans the AppleTalk network for all LaserPrinter servers
- | and displays them in a list. This is the Beta-test for a project which
- | I'm working on currently. I though it might be of interest to those
- | exploring the preferred AppleTalk interface.
- |
- | <c>1991 Mike Carter, MCDesign. You may use portions of this code if you like,
- | as long as authorship is acknowledged. Bug reports and any (and all) comments
- | are welcome! You can reach me via E-Mail at CompuServe 76114,321.
- |
- | 'FindPrinters' is a trademark of MCDesign. All rightrs reserved.
- |
- | (Be sure to include these libraries in your project: AppleTalk, nAppleTalk, MacTraps)
-
- #endif
-
- #define SEARCH 1 /* Dialog items */
- #define LIST 2
- #define NUMFOUND 3
- #define DONE 4
- #define LINE 8
- #define ICON 9
- #define MSG 10
-
- #define LOOKING 1 /* Message strings */
- #define LOOKUPERR 2
- #define EXTRACTERR 3
- #define NO_DEVICES 4
- #define ALL_DONE 5
-
- #define BASE_RES 128
- #define NIL_POINTER 0L
- #define WNE_TRAP_NUM 0x60
- #define UNIMPL_TRAP_NUM 0x9F
-
- #include <nAppleTalk.h>
-
- void DrawTheLine( DialogPtr theDlog ); /* Draws a dotted line on a userItem */
- void DoAlert( short ); /* Changes message area in DLOG */
- int findPrinters( Str32 *, short * ); /* does all the ATP stuff */
-
- Str32 theObj = "\p="; /* Anything... */
- Str32 theType = "\pLaserWriter"; /* of type LaserPrinter... */
- Str32 theZone = "\p*"; /* in our zone. */
- DialogPtr mainDlog;
- GrafPtr oldPort;
- short maxToGet = 25; /* max number to find */
- short numFound = 0; /* number found in search */
-
- Str32 pNames[25]; /* array for found printers */
- ListHandle theListH;
- Boolean gDone = false;
- Boolean gWNElmplemented;
- EventRecord gTheEvent;
- Ptr theBuff, ePtr; /* NBP receive buffer; entity pointer */
- int buffSize; /* size of buffer */
- CursHandle WatchCursor;
- Str255 brag = "\pFindPrinters <c>1991 MCDesign. Written by Mike Carter (76114,321) in Think C";
-
-
- /*********************** main *****************************/
- main()
- {
- MaxApplZone(); /* get some ROOM!!!! */
- InitMac(); /* initialize Mac Managers */
-
- /* Allocate our main memory-gobbling structures so they end */
- /* up at the bottom of our heap, causing much less heap */
- /* fragmentation. I call this semi-dynamic allocation! */
-
- buffSize = (sizeof( EntityName ) + 4) * maxToGet;
-
- theBuff = NewPtrClear( buffSize );
- if( theBuff == 0L )
- ExitToShell(); /* No memory!! */
-
- ePtr = NewPtrClear( 100 ); /* size for NBPSetentitiy */
- if( ePtr == 0L )
- ExitToShell(); /* no memory!! */
-
- SetUpDlog(); /* load and show our main dialog */
-
- LoopTheLoop(); /* main event loop */
-
- /* clean-up routines */
- LDispose( theListH ); /* Can't say whether or not these */
- DisposPtr( ePtr ); /* are _really_ necessary, seeing */
- DisposPtr( theBuff ); /* that quitting the app. releases */
- DisposDialog( mainDlog ); /* it's memory anyway--but what the */
- /* heck! can't hurt!! */
-
- SetPort( oldPort ); /* Set the GrafPort back the way we found it */
-
- ExitToShell(); /* ta-ta for now */
- }
-
- /*********************** InitMac **************************/
- InitMac()
- {
- InitGraf( &thePort ); /* Initialize the Mac Managers */
- InitFonts();
- FlushEvents( everyEvent, 0 );
- InitWindows();
- InitMenus();
- TEInit();
- InitDialogs( 0L );
- InitCursor();
-
- WatchCursor=GetCursor( watchCursor );
- HNoPurge((Handle)WatchCursor);
- }
-
- /******************** SetUpDlog *****************************/
- SetUpDlog()
- {
- int type = 0, hit = 0;
- Rect box;
- Handle itemH;
-
- mainDlog = GetNewDialog( BASE_RES + 1, 0L, -1L ); /* Get our main Dialog */
- if( mainDlog == 0L )
- ExitToShell();
-
- GetPort( &oldPort ); /* Let's be port-friendly */
- SetPort( mainDlog );
-
- SetUpList(); /* define the list which shows the printer names */
-
- ShowWindow( mainDlog ); /* become visual reality */
- DrawDialog( mainDlog ); /* draw the guts */
-
- FrameListRect(); /* frame the list's rect */
-
- DrawButton( mainDlog ); /* outline the default button */
- DrawTheLine( mainDlog ); /* draw the line seperating the message area */
- }
-
- /****************** SetUpList ********************************/
- SetUpList()
- {
- int type, i;
- Rect box, dataBounds, rView;
- Point cSize;
- Handle itemH;
- Cell theCell;
-
- GetDItem( mainDlog, LIST, &type, &itemH, &box );
-
- rView = box; /* Get rect size from our DITL user item */
- rView.left+=1; /* leave room for framerect */
- rView.right-=16; /* room for scrool bar and framerect */
- rView.bottom -= 1; /* room for framerect */
-
- cSize.h = rView.right - rView.left; /* set cell size */
- cSize.v = (rView.bottom - rView.top) / 6; /* show 6 cells at a time */
-
- SetRect(&dataBounds,0,0,1,maxToGet); /* define cell structure */
-
- theListH = LNew(&rView, &dataBounds, cSize, 0L, mainDlog, true, false, false, true);
- (**theListH).selFlags = lOnlyOne+lNoDisjoint+lNoExtend+lNoNilHilite;
-
- }
-
- /**************************** LoopTheLoop ***************************/
- LoopTheLoop()
- {
- /* MAIN LOOP SEGMENT!!!!!
- *
- * Is WaitNextEvent() implemented? If it is, the address of the
- * WaitNextEvent() trap will be different than the standard,
- * "unimplemented" trap...
- */
-
- gWNElmplemented = ( NGetTrapAddress( WNE_TRAP_NUM, ToolTrap ) !=
- NGetTrapAddress( UNIMPL_TRAP_NUM, ToolTrap ) );
-
- /*
- * Don't wait for a mouse click. Retrieve and process events
- * instead!
- */
-
- while ( gDone == false )
- {
- HandleEvent();
- }
- }
-
- /************************** HandleEvent *****************************/
- HandleEvent()
- {
- int theItem, type;
- Handle itemH;
- Rect box;
- Point pt;
- int err = 0;
-
- if ( gWNElmplemented ) /* Use appropriate event routine */
- WaitNextEvent( everyEvent, &gTheEvent, 0L, 0L );
-
- else
- {
- SystemTask();
- GetNextEvent( everyEvent, &gTheEvent );
- }
-
- if (IsDialogEvent( &gTheEvent ) ) /* event happened inside the Dlog?? */
- {
- if ( DialogSelect( &gTheEvent, &mainDlog, &theItem ) ) /* yes it did!! */
- {
- switch( theItem )
- {
- case SEARCH:
- SetCursor(*WatchCursor);
- err = findPrinters( pNames, &numFound );
- InitCursor();
- if( err != noErr)
- SysBeep( 30 );
- break;
-
- case DONE:
- gDone = true;
- return; /* fall all the out to LoopTheLoop */
- break;
-
- case LIST:
- pt = gTheEvent.where;
- GlobalToLocal( &pt );
- LClick( pt, gTheEvent.modifiers, theListH );
- break;
-
- case ICON:
- GetDItem( mainDlog, MSG, &type, &itemH, &box ); /* secret brag switch! */
- SetIText( itemH, &brag );
- break;
- }
- gTheEvent.what = nullEvent; /* so the following switch won't handle it */
- }
- }
-
- switch ( gTheEvent.what ) /* Okay, event wasn't part of dialog */
- {
- case nullEvent:
- break;
-
- case mouseDown:
- HandleMouseDown();
- break;
-
- case keyDown: /* don't need to list them */
- case keyUp:
- case autoKey:
- break;
-
- case updateEvt:
- BeginUpdate( gTheEvent.message );
- DrawDialog( mainDlog );
- FrameListRect();
- EndUpdate( gTheEvent.message );
- break;
- }
- }
-
- /*********************** HandleMouseDown ******************/
- HandleMouseDown()
- {
- WindowPtr whichWindow;
- short int thePart;
- long windSize;
- GrafPtr oldPort;
- Rect dragRect = screenBits.bounds;
-
- /* First, find out which window the mouse click occurred in.
- * Then, find out what part of the window the mouse click occurred in.
- */
-
- thePart = FindWindow( gTheEvent.where, &whichWindow );
- switch ( thePart )
- {
- case inSysWindow : /* Probably a desk accessory window... */
- SystemClick( &gTheEvent, whichWindow );
- break;
-
- case inDrag: /* Drag the window around the screen, limited by dragRect */
- DragWindow( whichWindow, gTheEvent.where, &dragRect);
- break;
- }
- }
-
- /**************************** FrameListRec **************************/
- FrameListRect()
- {
- int type;
- Rect box;
- Handle itemH;
-
- GetDItem( mainDlog, LIST, &type, &itemH, &box );
- box.top -= 1;
- FrameRect( &box );
-
- DisposHandle( itemH );
- }
-
- /************************** findPrinters ****************************/
- int findPrinters( Str32 *pNames, short *numFound)
- {
- EntityName aFoundPrinter; /* holds info for found printers */
- AddrBlock entityAddr; /* address for found printers */
- int type = 0, i = 0; /* Dlog stuff */
- long dummy; /* Delay() dummy var */
- Handle itemH; /* Dlog stuff */
- Rect box; /* ditto. */
- Str255 look, numStr; /* a mesage */
- MPPParamBlock p; /* preferred interface paramBlock */
- Ptr ePtr; /* pointer to entity stuff */
- OSErr err; /* OS err value */
- Cell theCell; /* for the Dlog list */
-
- GetIndString( &look, BASE_RES, LOOKING ); /* load a message */
- GetDItem( mainDlog, MSG, &type, &itemH, &box );
- SetIText( itemH, &look );
-
-
- NBPSetEntity( ePtr, theObj, theType, theZone ); /* setup up the entity */
-
- p.ioCompletion = 0L; /* no completion procedure */
- p.NBPinterval = 2; /* interval of two */
- p.NBPcount = 3; /* retry three times only */
- p.NBPentityPtr = ePtr; /* the entity info */
- p.NBPretBuffPtr = theBuff; /* return buffer */
- p.NBPretBuffSize = buffSize;
- p.NBPmaxToGet = maxToGet; /* maximum entities to find */
-
- err = PLookupName( &p, false ); /* go lookin' */
- if( err != noErr )
- {
- DoAlert( LOOKUPERR );
- return( -1 );
- }
-
- if( p.NBPnumGotten <= 0 )
- {
- DoAlert( NO_DEVICES ); /* error code for none found */
- return( -1 );
- }
-
- NumToString( p.NBPnumGotten, &numStr );
- GetDItem( mainDlog, NUMFOUND, &type, &itemH, &box );
- SetIText( itemH, &numStr );
-
- for( i = 1; i <= p.NBPnumGotten; i++ ) /* cycle thru and extract */
- {
- err = NBPExtract( theBuff, p.NBPnumGotten, i, &aFoundPrinter, &entityAddr );
- if( err != noErr )
- {
- DoAlert( EXTRACTERR );
- return( -1 );
- }
-
- BlockMove( (Ptr)&aFoundPrinter.objStr, (Ptr)&pNames[i], aFoundPrinter.objStr[0] );
- theCell.h = 0; theCell.v = i - 1;
- LSetCell( (Ptr)&aFoundPrinter.objStr[1], aFoundPrinter.objStr[0], theCell, theListH );
- LDraw( theCell, theListH );
- }
-
- GetIndString( &look, BASE_RES, ALL_DONE ); /* load a message */
- GetDItem( mainDlog, MSG, &type, &itemH, &box );
- SetIText( itemH, &look );
-
- return( 0 ); /* all is well */
- }
-
- /*********************** DoAlert ************************/
- void DoAlert( short index )
- {
- int type;
- Rect box;
- Handle itemH;
- Str255 errStr;
-
- GetDItem( mainDlog, MSG, &type, &itemH, &box );
- GetIndString( &errStr, BASE_RES, index );
-
- SetIText( itemH, &errStr );
- DisposHandle( itemH );
- }
-
-
- /********************** DrawTheLine ***********************/
- void DrawTheLine( DialogPtr theDlog )
- /*
- | This function will, utilizing the Rect defined in the user item
- | within the rez file, draw a dotted line to seperate the message
- | line at the bottom of the DLOG from the parts above it.
- */
- {
- Handle itemH;
- Rect box, theRect;
- Point where, left, right;
- int type;
-
- GetDItem( theDlog, LINE, &type, &itemH, &box );
-
- PenPat( ltGray );
- PenSize( 1, 1 );
-
- MoveTo( box.left, box.top );
- LineTo( box.right, box.top );
-
- PenNormal();
- }
-
- /*************************** ButtonDraw ****************/
- DrawButton( theDialog )
- DialogPtr theDialog;
- {
- int itemType;
- Rect itemRect;
- Handle item;
- GrafPtr oldPort;
-
- GetDItem( theDialog, SEARCH, &itemType, &item, &itemRect );
- GetPort( &oldPort );
- SetPort( theDialog );
-
- PenSize( 3,3 );
- InsetRect( &itemRect, -4, -4 );
- FrameRoundRect( &itemRect, 16, 16 );
- PenNormal();
-
- SetPort( oldPort );
- }